﻿#region

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.UI;
using System.Web.UI.WebControls;
using BLL;
using DAL;
using RenrenApi;

#endregion

namespace Web
{
    public partial class PageCourse : Page
    {
        private const int PageSize = 5;
        protected Course CurrentCourse; // 当前课程
        protected RenrenApiClient RenrenClient;
        private AllThing _allThing;
        private CourseBll _courseBll;
        private UserThingBll _userThingBll;

        private int PageCount // 分页总页数
        {
            get { return (int) ViewState["PageCount"]; }
            set { ViewState["PageCount"] = value; }
        }

        private int CurrentPage // 当前页码
        {
            get { return (int) ViewState["CurrentPage"]; }
            set { ViewState["CurrentPage"] = value; }
        }

        private string TabState // 标签的状态
        {
            get { return (string) ViewState["TabState"]; }
            set { ViewState["TabState"] = value; }
        }

        private bool IsReplyClicked // 回复按钮是否点击
        {
            get
            {
                if (ViewState["IsReplyClicked"] == null)
                    ViewState["IsReplyClicked"] = false;
                return (bool) ViewState["IsReplyClicked"];
            }
            set { ViewState["IsReplyClicked"] = value; }
        }

        #region 初始化

        protected void Page_Load(object sender, EventArgs e)
        {
            if (Session["client"] == null) // 未授权
            {
                Response.Redirect("index.aspx?redirect=" + Request.RawUrl);
                return;
            }
            RenrenClient = (RenrenApiClient)Session["client"];
            //    ?? new RenrenApiClient("246340810", "2.4df2b5cb74006d496feae0eb2efb3320.3600.1315213200-246340810");
            // 获取ID
            string id = Request["id"];
            _courseBll = new CourseBll(int.Parse(id), !IsPostBack);
            CurrentCourse = _courseBll.GetCourse();
            _userThingBll = new UserThingBll(RenrenClient.Uid, id, CurrentCourse.CourseInfo);
            _allThing = new AllThing
                            {
                                ClassId = id,
                                ClassName = CurrentCourse.CourseName,
                                UserId = RenrenClient.Uid,
                                UserName = RenrenClient.UserName,
                                UserPic = RenrenClient.UserPic,
                                Post = "",
                                Reply = "",
                                Place = ""
                            };
            Initialize();
        }

        // 各种初始化
        private void Initialize()
        {
            InitExisting();
            InitRecommendation();
            InitCourseType();
            InitDiscuss();
            InitScore();
            InitPlace();
            InitSameNameCourse();
            InitJS();
            InitUserVisit();
        }

        // 是否开课
        private void InitExisting()
        {
            if (!CurrentCourse.IsExisting)
            {
                NotExist.Text =
                    "<div style=\"display:inline; margin-left:6px; font-size:14px; color:#998675;\">本学期未开设</div>";
                AskForHelpButton.Enabled = false;
            }
        }

        // 记录访问
        private void InitUserVisit()
        {
            if (!IsPostBack)
                _userThingBll.Visit();
        }

        // 初始化同名课程
        private void InitSameNameCourse()
        {
            int total;
            SameNameCourses.DataSource = _courseBll.GetSameNameCourses(8, out total);
            SameNameCourses.DataBind();
            SameNameCourseNum.Text = total.ToString();
            if (total == 0)
                SameNameCoursePanel.Visible = false;
        }

        // 初始化js脚本
        private void InitJS()
        {
            // 附加人人js
            ClientScript.RegisterClientScriptBlock(GetType(), "SendFeed",
                                                   RenrenClient.GetSendFeedScript(Request["id"],
                                                                                      CurrentCourse.CourseName,
                                                                                      CurrentCourse.Introduction));
            // 还原可展开项
            ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "FixCollapse", "fixCollaspe();", true);
        }

        // 初始化课程类型
        private void InitCourseType()
        {
            if (!CurrentCourse.Type.Equals(""))
                CourseType.Text = string.Format("<li><span>课程类型</span>{0}</li>", CurrentCourse.Type);
        }

        #endregion

        // 顶部搜索按钮
        protected void HeaderSearchBox_Click(object sender, EventArgs e)
        {
            Response.Redirect("search.aspx?type=10&value=" + search_input.Text);
        }

        #region 推荐

        private void InitRecommendation()
        {
            // 修改推荐按钮
            if (_userThingBll.HasRecommended())
                DisableRcmdButton();
            // 设置推荐数量
            RcmdNum.Text = CurrentCourse.CourseInfo.RcmdNum.ToString();
        }

        // 禁用推荐按钮
        private void DisableRcmdButton()
        {
            RcmdButton.Text = "已推荐";
            RcmdButton.Style.Clear();
            RcmdButton.Style.Add("background-position", "-207px 0");
            RcmdButton.OnClientClick = "return false;";
        }

        // 点击推荐按钮
        protected void RcmdButton_Click(object sender, EventArgs e)
        {
            _allThing.Type = (int) NewsType.Recommended;
            AllThingBll.Insert(_allThing, RenrenClient);
            RcmdNum.Text = _userThingBll.Recommend().ToString(); // 发送推荐请求
            DisableRcmdButton();
            ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "RcmdSend",
                                                RenrenClient.GetSendFeedFunctionName(FeedType.Recommendation), true);
        }

        #endregion

        #region 分页

        // 设置分页
        private void SetPageIndicator(int pageCount)
        {
            if (pageCount == 0)
            {
                ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "HidePageIndicator",
                                                    "$('#page_indicator').hide();$('.line_mid').hide();", true);
                return;
            }
            ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "ShowPageIndicator",
                                                "$('#page_indicator').show();$('.line_mid').show();", true);
            page_down.Visible = (pageCount > 1);
            PageIndicator.DataSource = new int[pageCount];
            PageIndicator.DataBind();
        }

        // 填充分页数据
        protected void PageDataBound(object sender, RepeaterItemEventArgs e)
        {
            if (e.Item.ItemType != ListItemType.Item && e.Item.ItemType != ListItemType.AlternatingItem)
                return;
            int page = e.Item.ItemIndex + 1;
            if (page != CurrentPage)
            {
                var linkButton = new LinkButton
                                     {
                                         ID = "page" + page,
                                         Text = string.Format("<li>{0}</li>", page),
                                         OnClientClick = "$('#DiscussArea').fadeTo(300, 0);discussAnimation=true;"
                                     };
                linkButton.Click += PageClick;
                ToolkitScriptManager1.RegisterAsyncPostBackControl(linkButton);
                e.Item.FindControl("item").Controls.Add(linkButton);
            }
            else
                e.Item.FindControl("item").Controls.Add(new Literal {Text = string.Format("<li>{0}</li>", page)});
        }

        // 点击页码
        private void PageClick(object sender, EventArgs e)
        {
            int page = int.Parse(((LinkButton) sender).ID.Substring(4));
            LoadPage(page);
        }

        /// <summary>
        /// 	加载新页
        /// </summary>
        /// <param name = "page">要加载的页码</param>
        private void LoadPage(int page)
        {
            LoadPage(page, TabState);
        }

        /// <summary>
        /// 	加载新页
        /// </summary>
        /// <param name = "page">要加载的页码</param>
        /// <param name = "type">类型</param>
        private void LoadPage(int page, string type)
        {
            CurrentPage = page;
            int pageCount = 0;
            switch (type)
            {
                case "help all":
                    LoadHelps(_courseBll.GetHelps(page, PageSize, out pageCount), "all", pageCount);
                    break;
                case "help mine":
                    LoadHelps(_courseBll.GetMyHelps(RenrenClient.Uid, page, PageSize, out pageCount), "mine",
                              pageCount);
                    break;
                case "help search":
                    LoadHelps(_courseBll.SearchHelps(SearchPostTextBox.Text, page, PageSize, out pageCount), "search",
                              pageCount);
                    break;
                case "chat all":
                    LoadChats(_courseBll.GetChats(page, PageSize, out pageCount), "all", pageCount);
                    break;
                case "chat mine":
                    LoadChats(_courseBll.GetMyChats(RenrenClient.Uid, page, PageSize, out pageCount), "mine",
                              pageCount);
                    break;
                case "chat search":
                    LoadChats(_courseBll.SearchChats(SearchPostTextBox.Text, page, PageSize, out pageCount), "search",
                              pageCount);
                    break;
            }
            PageCount = pageCount;
        }

        // 下一页
        protected void page_down_Click(object sender, EventArgs e)
        {
            LoadPage(CurrentPage + 1);
        }

        #endregion

        #region 评分

        // 设置评分栏及我的评分
        private void InitScore()
        {
            if (_userThingBll.HasScored())
                FillMyScore();
            else
            {
                my_rating.Visible = false;
                ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "SetupScore", "setupScore();", true);
            }
        }

        // 评分确定按钮
        protected void Score_Click(object sender, EventArgs e)
        {
            int gold = int.Parse(CourseGold.Text);
            int relax = int.Parse(CourseRelax.Text);
            int mark = int.Parse(CourseMark.Text);
            _userThingBll.Score(gold, relax, mark);
            _allThing.Type = (int) NewsType.Scored;
            AllThingBll.Insert(_allThing, RenrenClient);
            FillMyScore();
        }

        // 填充我的评分
        private void FillMyScore()
        {
            MyGold.Text = _userThingBll.MyGold.ToString();
            MyRelax.Text = _userThingBll.MyRelax.ToString();
            MyMark.Text = _userThingBll.MyMark.ToString();
            recommend.Style["top"] = "180px";
            my_rating.Visible = true;
            ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "ShowMyRating", "showScore();", true);
        }

        #endregion

        #region 地点

        // 设置地点栏
        private void InitPlace()
        {
            if (_courseBll.HasPlace())
                ShowPlaces(false /*不显示动画*/);
        }

        // 发布地点
        protected void PlacePublish_Click(object sender, EventArgs e)
        {
            if (place_input.Text.Length <= 5)
                return;
            _allThing.Place = place_input.Text;
            _allThing.Type = (int) NewsType.AddPlace;
            AllThingBll.Insert(_allThing, RenrenClient);
            _courseBll.PulishPlace(place_input.Text, RenrenClient.Uid, RenrenClient.UserName);
            ShowPlaces(true);
        }

        // 绘制地点信息
        private void ShowPlaces(bool animated)
        {
            // 绑定数据
            var places = CurrentCourse.CoursePlaces.OrderByDescending(coursePlace => coursePlace.EditTime);
            var histories = places.Skip(1).ToList();
            HistoryRepeater.DataSource = histories;
            HistoryRepeater.DataBind();
            ShowFirstPlace(places.First());
            SetHistoryPlaceBar(histories.Count + 1);
            // 绘制到页面
            ScriptManager.RegisterStartupScript(UpdatePanel1,
                                                GetType(),
                                                "ShowPlace",
                                                animated ? "showAnimatedPlaces();" : "showNormalPlaces();",
                                                true);
        }

        // 设置地点下拉条，并更新计数
        private void SetHistoryPlaceBar(int placesCount)
        {
            if (placesCount >= 2)
            {
                quiz_num.Controls.Clear();
                quiz_num.Controls.Add(new Literal {Text = placesCount.ToString()});
                ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "ShowHistoryBar",
                                                    "$('#expand_history').show();", true);
            }
            else // 不显示
                ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "HideHistoryBar",
                                                    "$('#expand_history').hide();", true);
        }

        // 显示第一个地点
        private void ShowFirstPlace(CoursePlcace coursePlcace)
        {
            PlaceLabel.Text = coursePlcace.Place;
            PlacePublishDate.Text = coursePlcace.EditTime.ToLongDateString();
            PlacePublisher.Text = string.Format("<a href=\"{0}\" target=\"_blank\">{1}</a>", Utility.GetRenrenUrl(coursePlcace.EditorId),
                                                coursePlcace.EditorName);
            PlacePublisherImg.Text =
                string.Format("<a href=\"{0}\" target=\"_blank\"><img src=\"{1}\" width=\"50\" height=\"50\" /></a>",
                Utility.GetRenrenUrl(coursePlcace.EditorId), UserThingBll.GetPic(coursePlcace.EditorId));
        }

        // 求助
        protected void AskForHelpButton_Click(object sender, EventArgs e)
        {
            _allThing.Type = (int) NewsType.AskForPlace;
            AllThingBll.Insert(_allThing, RenrenClient);
            ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "AskForPlaceSend",
                                                RenrenClient.GetSendFeedFunctionName(FeedType.AskForPlace), true);
        }

        #endregion

        #region 讨论区

        #region 功能

        // 初始化
        private void InitDiscuss()
        {
            if (TabState == null) // 第一次访问，加载求助
                tab_help_Click(null, null);
            else // 不是第一次，只设置分页器
                SetPageIndicator(PageCount);
        }

        // 搜索帖子按钮
        protected void search_post_Click(object sender, EventArgs e)
        {
            LoadPage(1, TabState.Split(' ')[0] + " search");
        }

        // 我的帖子
        protected void LinkButton1_Click(object sender, EventArgs e)
        {
            LoadPage(1, TabState.Split(' ')[0] + " mine");
        }

        // 点击发帖按钮
        protected void PublishButton_Click(object sender, EventArgs e)
        {
            if (NewPostArea.Text == "")
                return;
            string type = TabState.Split(' ')[0];
            switch (type)
            {
                case "help":
                    _courseBll.PostHelp(NewPostArea.Text, RenrenClient.Uid, RenrenClient.UserName,
                                        RenrenClient.UserPic);
                    break;
                case "chat":
                    _courseBll.PostChat(NewPostArea.Text, RenrenClient.Uid, RenrenClient.UserName,
                                        RenrenClient.UserPic);
                    break;
            }
            _allThing.Post = NewPostArea.Text;
            _allThing.Type = (int) NewsType.AddPost;
            AllThingBll.Insert(_allThing, RenrenClient);
            NewPostArea.Text = "";
            LoadPage(CurrentPage);
            var replyItemId = type + "_item0";
            ScriptManager.RegisterStartupScript(UpdatePanel1,
                                                GetType(),
                                                "ShowPost" + replyItemId,
                                                string.Format(
                                                    "$('#{0}').attr('height','0');$('#{0}').slideDown();",
                                                    replyItemId),
                                                true);
            if (SendNews.Checked)
                ScriptManager.RegisterStartupScript(UpdatePanel1, GetType(), "RcmdSend",
                                                RenrenClient.GetSendFeedFunctionName(FeedType.Comment), true);
        }

        #endregion

        #region 闲聊

        // 闲聊按钮
        protected void tab_chat_Click(object sender, EventArgs e)
        {
            // 修改求助和闲谈按钮的css
            tab_help.Style["background-position"] = "0 0";
            tab_chat.Style["background-position"] = "-195px -25px";
            // 加载闲聊
            LoadPage(1, "chat all");
            // 设置选项卡状态
            Chats.Visible = true;
            Helps.Visible = false;
            // 设置发帖提示
            NewPostAreaWatermark.WatermarkText = "各种扯、各种谈、各种水…";
        }

        /// <summary>
        /// 	加载闲聊
        /// </summary>
        /// <param name = "data">数据</param>
        /// <param name = "type">类型</param>
        /// <param name = "pageCount">总页数</param>
        private void LoadChats(List<Chat> data, string type, int pageCount)
        {
            if (IsReplyClicked)
            {
                Chats.DataSource = Session["chats"];
                IsReplyClicked = false;
            }
            else
            {
                Chats.DataSource = data;
                Session["chats"] = data;
            }
            Chats.DataBind();
            SetPageIndicator(pageCount);
            TabState = "chat " + type;
        }

        // 绑定聊天
        protected void ChatsItemBound(object sender, RepeaterItemEventArgs e)
        {
            if (e.Item.ItemType != ListItemType.Item && e.Item.ItemType != ListItemType.AlternatingItem)
                return;
            var chat = e.Item.DataItem as Chat;
            // 绑定回复
            var repeater = e.Item.FindControl("replies") as Repeater;
            repeater.DataSource = chat.ChatReplys;
            repeater.DataBind();
        }

        // 聊天回复
        protected void ChatReplyClick(object sender, EventArgs e)
        {
            var button = sender as Button;
            int chatId = int.Parse(button.Text);
            var textBox = button.Parent.FindControl("ChatReplyArea") as TextBox;
            string content = textBox.Text;
            if (content == "")
                return;
            var chatReply = new ChatReply
                                {
                                    Content = content,
                                    Time = DateTime.Now,
                                    UserId = RenrenClient.Uid,
                                    UserName = RenrenClient.UserName,
                                    UserPic = RenrenClient.UserPic,
                                    ChatID = chatId
                                };
            _courseBll.HelpReply(chatReply);
            _allThing.Reply = content;
            _allThing.Post = CurrentCourse.Chats.Single(c => c.ID == chatId).Content;
            _allThing.Type = (int) NewsType.Reply;
            AllThingBll.Insert(_allThing, RenrenClient);
            DrawChatNewReply(chatId, textBox.ClientID, chatReply);
        }

        // 绘制新回复
        private void DrawChatNewReply(int chatId, string textBoxId, ChatReply chatReply)
        {
            IsReplyClicked = true;
            var chat = ((List<Chat>) Session["chats"]).Single(h => h.ID == chatId);
            chat.UpdateTime = DateTime.Now;
            chat.ChatReplys.Add(chatReply);
            LoadPage(CurrentPage);
            string replyItemId = string.Format("chat_replyitem{0}_{1}",
                                               chatId,
                                               CurrentCourse.Chats.Single(c => c.ID == chatId)
                                                   .ChatReplys.Count - 1);
            ScriptManager.RegisterStartupScript(UpdatePanel1,
                                                GetType(),
                                                "AddChatReply" + replyItemId,
                                                string.Format(
                                                    "$('#{0}').val('');$('#{1}').hide();$('#{1}').slideDown();",
                                                    textBoxId,
                                                    replyItemId),
                                                true);
        }

        #endregion

        #region 求助

        // 求助按钮
        protected void tab_help_Click(object sender, EventArgs e)
        {
            // 修改求助和闲谈按钮的css
            tab_help.Style["background-position"] = "-195px 0";
            tab_chat.Style["background-position"] = "0 -25px";
            // 加载求助
            LoadPage(1, "help all");
            // 设置选项卡状态
            Helps.Visible = true;
            Chats.Visible = false;
            // 设置发帖提示
            NewPostAreaWatermark.WatermarkText = "求换课、求课件、求C语言作业、各种求…";
        }

        /// <summary>
        /// 	加载求助
        /// </summary>
        /// <param name = "data">数据</param>
        /// <param name = "type">类型</param>
        /// <param name = "pageCount">总页数</param>
        private void LoadHelps(List<Help> data, string type, int pageCount)
        {
            if (IsReplyClicked)
            {
                Helps.DataSource = Session["helps"];
                IsReplyClicked = false;
            }
            else
            {
                Helps.DataSource = data;
                Session["helps"] = data;
            }
            Helps.DataBind();
            SetPageIndicator(pageCount);
            TabState = "help " + type;
        }

        // 绑定求助
        protected void HelpsItemBound(object sender, RepeaterItemEventArgs e)
        {
            if (e.Item.ItemType != ListItemType.Item && e.Item.ItemType != ListItemType.AlternatingItem)
                return;
            var help = e.Item.DataItem as Help;
            // 绑定回复
            var repeater = e.Item.FindControl("replies") as Repeater;
            repeater.DataSource = help.HelpReplys;
            repeater.DataBind();
        }

        // 求助回复
        protected void HelpReplyClick(object sender, EventArgs e)
        {
            var button = sender as Button;
            int helpId = int.Parse(button.Text);
            var textBox = button.Parent.FindControl("HelpReplyArea") as TextBox;
            string content = textBox.Text;
            if (content == "")
                return;
            var helpReply = new HelpReply
                                {
                                    Content = content,
                                    Time = DateTime.Now,
                                    UserId = RenrenClient.Uid,
                                    UserName = RenrenClient.UserName,
                                    UserPic = RenrenClient.UserPic,
                                    HelpID = helpId
                                };
            _courseBll.HelpReply(helpReply);
            _allThing.Reply = content;
            _allThing.Post = CurrentCourse.Helps.Single(c => c.ID == helpId).Content;
            _allThing.Type = (int) NewsType.Reply;
            AllThingBll.Insert(_allThing, RenrenClient);
            DrawHelpNewReply(helpId, textBox.ClientID, helpReply);
        }

        // 绘制新回复
        private void DrawHelpNewReply(int helpId, string textBoxId, HelpReply helpReply)
        {
            IsReplyClicked = true;
            var help = ((List<Help>) Session["helps"]).Single(h => h.ID == helpId);
            help.UpdateTime = DateTime.Now;
            help.HelpReplys.Add(helpReply);
            LoadPage(CurrentPage);
            string replyItemId = string.Format("help_replyitem{0}_{1}",
                                               helpId,
                                               CurrentCourse.Helps.Single(c => c.ID == helpId)
                                                   .HelpReplys.Count - 1);
            ScriptManager.RegisterStartupScript(UpdatePanel1,
                                                GetType(),
                                                "AddHelpReply" + replyItemId,
                                                string.Format(
                                                    "$('#{0}').val('');$('#{1}').hide();$('#{1}').slideDown();",
                                                    textBoxId,
                                                    replyItemId),
                                                true);
        }

        #endregion

        #endregion
    }
}